package co.yixiang.yshop.module.crm.service.crmworkwxcustomer;

import co.yixiang.yshop.framework.common.exception.ErrorCode;
import co.yixiang.yshop.module.crm.dal.dataobject.crmcustomer.CrmCustomerDO;
import co.yixiang.yshop.module.crm.dal.dataobject.crmworkwxconfig.CrmWorkWxConfigDO;
import co.yixiang.yshop.module.crm.dal.dataobject.crmworkwxuser.CrmWorkWxUserDO;
import co.yixiang.yshop.module.crm.dal.mysql.crmcustomer.CrmCustomerMapper;
import co.yixiang.yshop.module.crm.dal.mysql.crmworkwxuser.CrmWorkWxUserMapper;
import co.yixiang.yshop.module.crm.service.crmworkwxconfig.CrmWorkWxConfigService;
import co.yixiang.yshop.module.system.api.user.AdminUserApi;
import co.yixiang.yshop.module.system.api.user.dto.AdminUserRespDTO;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import lombok.extern.slf4j.Slf4j;
import me.chanjar.weixin.common.error.WxErrorException;
import me.chanjar.weixin.cp.api.impl.WxCpServiceImpl;
import me.chanjar.weixin.cp.bean.external.contact.ExternalContact;
import me.chanjar.weixin.cp.bean.external.contact.FollowedUser;
import me.chanjar.weixin.cp.bean.external.contact.WxCpExternalContactBatchInfo;
import me.chanjar.weixin.cp.config.impl.WxCpDefaultConfigImpl;
import org.dromara.hutool.core.text.StrUtil;
import org.springframework.stereotype.Service;
import jakarta.annotation.Resource;
import org.springframework.validation.annotation.Validated;
import org.springframework.transaction.annotation.Transactional;

import java.time.LocalDateTime;
import java.util.*;
import java.util.stream.Collectors;

import co.yixiang.yshop.module.crm.controller.admin.crmworkwxcustomer.vo.*;
import co.yixiang.yshop.module.crm.dal.dataobject.crmworkwxcustomer.CrmWorkWxCustomerDO;
import co.yixiang.yshop.framework.common.pojo.PageResult;
import co.yixiang.yshop.framework.common.pojo.PageParam;
import co.yixiang.yshop.framework.common.util.object.BeanUtils;

import co.yixiang.yshop.module.crm.dal.mysql.crmworkwxcustomer.CrmWorkWxCustomerMapper;

import static co.yixiang.yshop.framework.common.exception.util.ServiceExceptionUtil.exception;
import static co.yixiang.yshop.module.crm.enums.ErrorCodeConstants.*;

/**
 * 企业微信客户 Service 实现类
 *
 * @author yshop
 */
@Service
@Validated
@Slf4j
public class CrmWorkWxCustomerServiceImpl implements CrmWorkWxCustomerService {

    @Resource
    private CrmWorkWxCustomerMapper workWxCustomerMapper;
    @Resource
    private CrmWorkWxConfigService workWxConfigService;
    @Resource
    private CrmWorkWxUserMapper workWxUserMapper;
    @Resource
    private CrmCustomerMapper customerMapper;
    @Resource
    private AdminUserApi adminUserApi;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public void createWorkWxCustomer() {
        //同步客户之前需要同步员工
        List<CrmWorkWxUserDO> workWxUserDOS =  workWxUserMapper.selectList();
        if(workWxUserDOS == null || workWxUserDOS.isEmpty()){
            throw exception(new ErrorCode(202502111,"请先同步企业微信员工哦"));
        }
        List<String> userIds = workWxUserDOS.stream().map(CrmWorkWxUserDO::getUserid).collect(Collectors.toList());
        WxCpDefaultConfigImpl configStorage = new WxCpDefaultConfigImpl();
        CrmWorkWxConfigDO workWxConfig = workWxConfigService.getWorkWxConfig(0);
        configStorage.setCorpId(workWxConfig.getCorpId());
        configStorage.setAgentId(Integer.valueOf(workWxConfig.getAgentId()));
        configStorage.setCorpSecret(workWxConfig.getSecret());
        WxCpServiceImpl service = new WxCpServiceImpl();
        service.setWxCpConfigStorage(configStorage);
        try {
            WxCpExternalContactBatchInfo externalContactBatchInfo = service.getExternalContactService()
                    .getContactDetailBatch(userIds.toArray(new String[userIds.size()]),"",100);
            externalContactBatchInfo.getExternalContactList().forEach(row -> {
                ExternalContact externalContact = row.getExternalContact();
                FollowedUser followInfo = row.getFollowInfo();
                CrmWorkWxCustomerDO workWxCustomerDO = workWxCustomerMapper
                        .selectOne(new LambdaQueryWrapper<CrmWorkWxCustomerDO>()
                        .eq(CrmWorkWxCustomerDO::getExternalUserid,externalContact.getExternalUserId()));
                String customerName = StrUtil.isNotEmpty(externalContact.getCorpFullName())
                        ? externalContact.getCorpFullName() : externalContact.getName();
                String remarkMobile = followInfo.getRemarkMobiles() != null && followInfo.getRemarkMobiles().length > 0
                        ? followInfo.getRemarkMobiles()[0] : "--";

                if(workWxCustomerDO == null){
                    Long customerId = 0L;
                    //判断客户本地是否存在
                    CrmCustomerDO customerDO = customerMapper.selectOne(new LambdaQueryWrapper<CrmCustomerDO>()
                            .and(i->i.eq(CrmCustomerDO::getName,customerName).or().eq(CrmCustomerDO::getMobile,remarkMobile))
                            .orderByDesc(CrmCustomerDO::getId).last("limit 1"));
                    if(customerDO == null){
                        //获取员工adminId
                        CrmWorkWxUserDO crmWorkWxUserDO = workWxUserMapper
                                .selectOne(new LambdaQueryWrapper<CrmWorkWxUserDO>()
                                        .eq(CrmWorkWxUserDO::getUserid,followInfo.getUserId()));
                        CrmCustomerDO crmCustomerDO = CrmCustomerDO.builder()
                                .name(customerName)
                                .mobile(remarkMobile)
                                .telephone(remarkMobile)
                                .source(10) //10-企业微信
                                .ownerUserId(crmWorkWxUserDO.getAdminId())
                                .nextTime(LocalDateTime.now())
                                .followTime(LocalDateTime.now())
                                .collectTime(LocalDateTime.now())
                                .build();
                        customerMapper.insert(crmCustomerDO);
                        customerId = crmCustomerDO.getId();
                    }else{
                        customerId = customerDO.getId();
                    }
                    CrmWorkWxCustomerDO workWxCustomerDO2 = BeanUtils.toBean(externalContact,CrmWorkWxCustomerDO.class);
                    workWxCustomerDO2.setFollowUser(followInfo.getUserId());
                    workWxCustomerDO2.setCorpId(workWxConfig.getCorpId());
                    workWxCustomerDO2.setCustomerId(customerId);
                    workWxCustomerDO2.setExternalUserid(externalContact.getExternalUserId());

                    workWxCustomerMapper.insert(workWxCustomerDO2);
                }
            });
        }catch (WxErrorException e){
            log.error("同步企业微信客户失败:{}", e.getMessage());
            throw exception(new ErrorCode(202502110,"同步企业微信客户失败"));
        }


    }

    @Override
    public void updateWorkWxCustomer(CrmWorkWxCustomerSaveReqVO updateReqVO) {
        // 校验存在
        validateWorkWxCustomerExists(updateReqVO.getId());
        // 更新
        CrmWorkWxCustomerDO updateObj = BeanUtils.toBean(updateReqVO, CrmWorkWxCustomerDO.class);
        workWxCustomerMapper.updateById(updateObj);
    }

    @Override
    public void deleteWorkWxCustomer(Long id) {
        // 校验存在
        validateWorkWxCustomerExists(id);
        // 删除
        workWxCustomerMapper.deleteById(id);
    }

    private void validateWorkWxCustomerExists(Long id) {
        if (workWxCustomerMapper.selectById(id) == null) {
            throw exception(WORK_WX_CUSTOMER_NOT_EXISTS);
        }
    }

    @Override
    public CrmWorkWxCustomerDO getWorkWxCustomer(Long id) {
        return workWxCustomerMapper.selectById(id);
    }

    @Override
    public PageResult<CrmWorkWxCustomerRespVO> getWorkWxCustomerPage(CrmWorkWxCustomerPageReqVO pageReqVO) {
        PageResult<CrmWorkWxCustomerDO> pageResult = workWxCustomerMapper.selectPage(pageReqVO);
        PageResult<CrmWorkWxCustomerRespVO> pageResult1 = BeanUtils.toBean(pageResult, CrmWorkWxCustomerRespVO.class);
        pageResult1.getList().forEach(u -> {
            //填充归属员工信息
            CrmWorkWxUserDO crmWorkWxUserDO = workWxUserMapper
                    .selectOne(new LambdaQueryWrapper<CrmWorkWxUserDO>()
                            .eq(CrmWorkWxUserDO::getUserid,u.getFollowUser()));
            AdminUserRespDTO adminUserRespDTO = adminUserApi.getUser(crmWorkWxUserDO.getAdminId());
            u.setFollowUserName(adminUserRespDTO.getNickname());
            u.setFollowUserId(crmWorkWxUserDO.getAdminId());
            //填充客户信息
            CrmCustomerDO customerDO = customerMapper.selectById(u.getCustomerId());
            u.setCustomerName(customerDO.getName());
        });
        return pageResult1;
    }

}